.set KERNEL_LINEAR_BASE,		0xC0000000
.set kstack_size, 4 * 1024
.set dummy_sel,		0x00
.set kcode_sel, 	0x08
.set kdata_sel, 	0x10
.set ktss_sel,		0x18
.set ucode_sel,		0x23
.set udata_sel,		0x2B

.set desc_num,		8
.set desc_size,		8

.set gdt_len,		desc_num * desc_size


# struct _intr_handler intr_handler_array
.set intr_vector,	0x00
.set intr_hook,		0x04
.set intr_priv,		0x08
.set intr_type,		0x0C


#IDT struct 
.set gate_offset_l,	0x00
.set gate_selector,	0x02
.set gate_attr,		0x04
.set gate_offset_h,	0x06

.set gate_attr_dpl0,	0x8E00
.set gate_attr_dpl3,	0xEE00

.set idt_len,		0x400



# TSS struct
.set t_back_line,  	0
.set t_esp0,		4
.set t_ss0,		8
.set t_esp1,		12
.set t_ss1,		16
.set t_esp2,		20
.set t_ss2,		24
.set t_cr3,		28
.set t_eip,		32
.set t_eflags,		36
.set t_eax,		40
.set t_ecx,		44
.set t_edx,		48
.set t_ebx,		52
.set t_esp,		56
.set t_ebp,		60
.set t_esi,		64
.set t_edi,		68
.set t_es,		72
.set t_cs,		76
.set t_ss,		80
.set t_ds,		84
.set t_fs,		88
.set t_gs,		92
.set t_ldt,		96
.set t_trace,		100

# page setup related
.set page_size,		0x1000

.set invalid,		0xFFFF


.globl kern_pre_start
.section .kernel.pre.start
.code16

kern_pre_start:		
		movw %cs, %ax
		movw %ax,%es
		movw %ax,%ds
		
		#call get_mem_map
		
		subl $0x10, %esp
		
		call setup_8253
		call setup_8259a
		call setup_gdt
		call setup_idtr
		
_pre_protect:
		movl %cr0,%eax
		orl $0x00000001,%eax
		movl %eax,%cr0

		jmpl $kcode_sel, $_en_protect


#####################################################################
#               code16 subfunction			    	    #
#####################################################################
.set rate,	1193180
.set HZ,	100

.set ticks,	(rate / HZ)

setup_8253:
		pushl %ebp
		movl %esp, %ebp
		
		movb $0x36, %al
		outb %al, $0x43
		
		movw $ticks, %ax
		outb %al, $0x40
		
		shrw $0x08, %ax
		outb %al, $0x40
		
		movl %ebp, %esp
		popl %ebp
		ret
		
		
setup_8259a:
		pushl %ebp
		movl %esp, %ebp
		
		movb $0x11,%al	
		outb %al,$0x20
		.word 0x00eb,0x00eb
			
		outb %al,$0xA0
		.word 0x00eb,0x00eb
			
		movb $0x20,%al
		outb %al,$0x21
		.word 0x00eb,0x00eb

		movb $0x28,%al
		outb %al,$0xA1
		.word 0x00eb,0x00eb

		movb $0x04,%al
		outb %al,$0x21
		.word 0x00eb,0x00eb

		movb $0x02,%al
		outb %al,$0xA1
		.word 0x00eb,0x00eb

		movb $0x01,%al
		outb %al,$0x21
		.word 0x00eb,0x00eb

		outb %al,$0xA1
		.word 0x00eb,0x00eb
		
		movb $0xFF,%al
		outb %al,$0x21
		.word 0x00eb,0x00eb
		
		movb $0xFF,%al
		outb %al,$0xA1
		.word 0x00eb,0x00eb
		
		movl %ebp, %esp
		popl %ebp
		ret 
		
setup_gdt:
		pushl %ebp
		movl %esp, %ebp
		subl $0x10, %esp
		
		movw $gdt_len,(%esp)		
		movl $gdt_start, 2(%esp)
		lgdtl (%esp)

		movl %ebp, %esp
		popl %ebp
		ret
		
setup_idtr:	
		pushl %ebp
		movl %esp, %ebp
		subl $0x10, %esp
			
		movl $idt_len, (%esp)
		movl $idt_start, 2(%esp)
		
		cli		
		
		lidtl (%esp)
		
		movl %ebp, %esp
		popl %ebp
		ret
			

.code32
.extern main
.extern kprintf
.set TEST,	65
.set user_code_sel,		0x23
.set user_data_sel,		0x2B
.extern pre_setup_pd,pre_setup_pt,map_intr_handler,setup_tss
.extern kstack
_en_protect:
		movw $kdata_sel, %ax
		movw %ax, %ds
		movw %ax, %ss
		
		movl $kstack, %eax
		addl $kstack_size, %eax
		movl %eax, %esp
		
		subl $0x40, %esp
		
		call init_ktty
		
		call pre_setup_pd
		call pre_setup_pt

_pg_finished:
		movl $protect_msg,(%esp)
		call kprintf

		movl %esp, 8(%esp)
		movl $tss, 4(%esp)
		movl $ktss,(%esp)
		call setup_tss
		
		# make TSS ready
		movl $ktss_sel, %ax
		ltr %ax
		
		movl $idt_start, (%esp)
		call map_intr_handler
		
		movl $0x100000, %eax
		movl %eax, %cr3
		
		movl %cr0, %eax
		orl $0x80000000, %eax
		movl %eax, %cr0
		
		jmp _en_pre_page

		
_en_pre_page:
		movl $page_msg,(%esp)
		call kprintf
		
		#movl $0xC0000000, %eax
		#addl $_en_page, %eax
		
		#jmp *%eax

_en_page:
		sti
		
		xorl %eax, %eax
		xorl %ebx, %ebx
		xorl %ecx, %ecx
		
		#movl $user_space_code, %eax
		#addl $0xC0000000, %eax
		#movl $ucode_desc, %edx
		#addl $0xC0000000, %edx

_pre_to_user:
		#movw %ax, 2(%edx)
		#shrl $0x10, %eax
		#movb %al, 4(%edx)
		#movb %ah, 7(%edx)

_user_desc_finished:
		addl $0x04, %esp
		pushfl
		movl (%esp), %eax
		
		movl $0x2B, 16(%esp)
		movl %esp, 12(%esp)
		movl %eax, 8(%esp)
		movl $0x23, 4(%esp)
		movl $user_space_code, (%esp)
		
		iret
_loop:
		#jmp _loop
		
		int $TEST


.code32
.globl user_space_code		

user_space_code:
		xorl %eax, %eax
		xorl %ecx, %ecx
		xorl %edx, %edx
			
		int $TEST
		
		jmp user_space_code
			
		movb $0xFE,%al
		outb %al,$0x21
		.word 0x00eb,0x00eb
		
		movb $0xFF,%al
		outb %al,$0xa1
		.word 0x00eb,0x00eb
		
		sti
		
		call main
_forgood:
		jmp _forgood		

#####################################################################
#               no return here				    #
#####################################################################
		hlt
		
		
.section .gdt
.globl gdt_start

gdt_start:
dummy:	.word 0x0000
	.word 0x0000
	.word 0x0000
	.word 0x0000

kcode:	.word 0xFFFF
	.word 0x0000
	.byte 0x00
	.byte 0x98
	.byte 0xCF
	.byte 0x00

kdata:	.word 0xFFFF
	.word 0x0000
	.byte 0x00
	.byte 0x92
	.byte 0xCF
	.byte 0x00

ktss:	.word 0x0068
	.word 0x00
	.byte 0x00
	.byte 0x89
	.byte 0x00
	.byte 0x00
	
ucode_desc:
	.word 0xFFFF
	.word 0x00
	.byte 0x00
	.byte 0xF8
	.byte 0xCF
	.byte 0x00

udata_desc:	
	.word 0xFFFF
	.word 0x0000
	.byte 0x00
	.byte 0xF2
	.byte 0xCF
	.byte 0x00
	
reservd: .fill 0x02, 0x08, 0x00


.section .idt
.globl idt_start
idt_start:	.fill 0x80, 0x08, 0x0

.data
.globl tss		
tss:	.fill 0x34, 0x02, 0x00

protect_msg:	.asciz "now in protect mode\n"
page_msg:	.asciz "page enabled...\n"

# EOF



